/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package utilidades.autocompletar;

import java.util.ArrayList;
import java.util.List;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.concurrent.Service;
import javafx.concurrent.Task;
import javafx.concurrent.WorkerStateEvent;
import javafx.event.EventHandler;
import javafx.scene.control.ComboBox;
import javafx.scene.control.ContentDisplay;
import javafx.scene.control.Label;
import javafx.scene.control.ListCell;
import javafx.scene.control.ListView;
import javafx.scene.input.KeyCode;
import javafx.scene.input.KeyEvent;
import javafx.scene.layout.HBox;
import javafx.scene.text.Text;
import javafx.util.Callback;
import transervfx.Dato.Entidad.Localidad;
import transervfx.Dato.Entidad.Provincia;
import transervfx.Logica.GestorPais;

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
/**
 *
 * @author rocio
 */
public class ComboBoxAutoCompletar<T extends Object> extends ComboBox<T> {

    TareaRestringirDatos serv = new TareaRestringirDatos();
    private final static String colorFondoTextoSeleccionado = "YELLOW";
    private final static String colorTextoSeleccionado = "BLACK";
    private String textEscritura = "";
    private List<T> datosTotalesCombobox = new ArrayList();
    
    public ComboBoxAutoCompletar() {
        //super();

        this.setCellFactory(this.cellFactory);
        

        serv.setOnSucceeded(new EventHandler<WorkerStateEvent>() {
            @Override
            public void handle(WorkerStateEvent t) {
                setItems(serv.getValue());
               // show();
               }
        });
        
       this.addEventFilter(KeyEvent.ANY, new EventHandler<KeyEvent>() {
            public void handle(KeyEvent t) {
                 if (t.getCode() == KeyCode.SPACE) {
                     show();                
                 textEscritura = textEscritura + t.getText();
                    setPromptText(textEscritura);

                    if (serv.isRunning()) {
                        serv.cancel();
                    }
                    serv.restart();

                 }
            }
       });

        this.addEventFilter(KeyEvent.KEY_PRESSED, new EventHandler<KeyEvent>() {
            public void handle(KeyEvent t) {
                if (t.getCode() == KeyCode.BACK_SPACE) {
                  
                  if (!textEscritura.isEmpty()) {
                        textEscritura = textEscritura.substring(0, textEscritura.length() - 1);
                        setPromptText(textEscritura);

                        if (serv.isRunning()) {
                            serv.cancel();
                        }
                        serv.restart();
                      //  System.out.println(textEscritura);
                    }
                } else if (t.getText().matches("[a-zA-z0-9]")) {
                   
                    textEscritura = textEscritura + t.getText();
                    setPromptText(textEscritura);

                    if (serv.isRunning()) {
                        serv.cancel();
                    }
                    serv.restart();



                   // System.out.println("entra " + textEscritura);
                }


            }
        });

    
        this.valueProperty().addListener(escuchadorComboBox);
        //getEditor().textProperty().addListener(escucharImput);
    }
    private final ChangeListener<Object> escuchadorComboBox = new ChangeListener<Object>() {
        @Override
        public void changed(ObservableValue ov, Object t, Object t1) {
            if (t1 != null) {
                System.out.println("DATOS TOTALES distinto a null");
                
              
            }
            else{
                System.out.println("DATOS TOTALES IGUAL A NULL");
           
            
            }
        }
    };
    private final ChangeListener<String> escucharImput = new ChangeListener<String>() {
        @Override
        public void changed(ObservableValue ov, String t, String t1) {
        }
    };

    private void pintarTexto(HBox h, String contenido, String itemSeleccionado) {

        h.getChildren().clear();
        int tamTextSelect = itemSeleccionado.length();
        int ini = 0;
        int i = contenido.indexOf(itemSeleccionado);
        int fin = contenido.length();
        //  System.out.println("tamTextSelect: "+tamTextSelect+" INI "+ini+" i: "+i+" fin: "+fin);
        //si encontro el item
        if (i > -1) {
            //   System.out.println("1LO CONTIENE");
            //si es el inicio
            if (i == ini) {
                //    System.out.println("2ES EL INICIO");
                Label t = new Label(contenido.substring(ini, ini + tamTextSelect));
                t.setStyle("-fx-text-fill: " + colorTextoSeleccionado + ";-fx-background-color: " + this.colorFondoTextoSeleccionado + ";");
                //t.setFill(Color.RED);
                h.getChildren().add(t);
                //listR.add(contenido.substring(ini, ini+tamTextSelect));
                if (tamTextSelect == fin) {
                    //    System.out.println("3ES EL FINAL");
                    return;
                }
                // System.out.println("4NO ES EL FINAL");
                h.getChildren().add(new Text(contenido.substring(ini + tamTextSelect, fin)));
                //listR.add(contenido.substring(ini+tamTextSelect, fin));
            } else {
                //  System.out.println("5 NO ES EL INICIO");
                h.getChildren().add(new Text(contenido.substring(ini, i)));
                //  listR.add(contenido.substring(ini, i));
                Label t = new Label(contenido.substring(i, i + tamTextSelect));
                t.setStyle("-fx-text-fill: " + colorTextoSeleccionado + ";-fx-background-color: " + colorFondoTextoSeleccionado + ";");
                //t.setFill(Color.RED);
                h.getChildren().add(t);
                // h.getChildren().add(new Text(contenido.substring(i, i+tamTextSelect)));
                //listR.add(contenido.substring(i, i+tamTextSelect));
                if (i + tamTextSelect == fin) {
                    //       System.out.println("6 ES EL FINAL");
                    return;
                }
                // System.out.println("7 NO ES EL FINAL");
                h.getChildren().add(new Text(contenido.substring(i + tamTextSelect, fin)));
                // listR.add(contenido.substring(i+tamTextSelect, fin));              
            }

        } else {
            h.getChildren().add(new Text(contenido));
        }


    }

   

    
    public void setData(ObservableList<T> list) {
        this.setPromptText("");
        this.textEscritura="";
        this.datosTotalesCombobox = list;
        this.setItems(FXCollections.observableArrayList(list));
    }
    
     public void setData(List<T> list) {
        this.setPromptText("");
        this.textEscritura="";
        this.datosTotalesCombobox = list;
        this.setItems(FXCollections.observableArrayList(list));
    }

    
    Callback cellFactory = new Callback<ListView<T>, ListCell<T>>() {
        @Override
        public ListCell<T> call(ListView<T> param) {
            final ListCell<T> cell = new ListCell<T>() {
                private HBox celda;

                {
                    super.setPrefWidth(100);
                    setContentDisplay(ContentDisplay.GRAPHIC_ONLY);
                    celda = new HBox();
                }

                @Override
                public void updateItem(T item,
                        boolean empty) {
                    super.updateItem(item, empty);

                    if (item == null || empty) {
                        celda.getChildren().clear();
                        return;
                    }

                    if (item != null) {

                        pintarTexto(celda, item.toString().toUpperCase(), textEscritura.toUpperCase());
                        setGraphic(celda);

                    }
                }
            };
            return cell;
        }
    };

  
   
    

    private class TareaRestringirDatos extends Service<ObservableList<T>> {

        protected Task createTask() {

            return new Task<ObservableList<T>>() {
                @Override
                protected ObservableList<T> call() throws Exception {
                    updateMessage("Creo una nueva lista");
                    int size = datosTotalesCombobox.size();
                    ObservableList<T> results = FXCollections.observableArrayList(new ArrayList(size));

                    String t1 = textEscritura.toUpperCase();
                    String s;
                    for (T t : datosTotalesCombobox) {

                        if (isCancelled()) {
                           
                            break;
                        }
                        s = t.toString();


                        if (s.toUpperCase().contains(t1)) {

                            results.add(t);
                        }
                    }
                    return results;

                }
            };
        }
    }
    
    
   
}
